package sword.chapter1Integer;

/**
 * 整数除法
 * b 被除数
 * c 除数
 * q 能被整除多少次——商
 * v 临时记录除数c*q的值——最接近被除数的最大值，后面循环时还需要重新计算被除数（当前b - v得到新的b）
 * <p>
 * 示例
 * c = 2
 * q的值=2的多少次方   c*2零次方   c*2一次方  c*2二次方  c*2三次方
 * v                   2            4           8       16
 *
 * @author K
 * @date 2021-10-10 16:00
 */
public class S1ZhengShuChuFa {

    private static int divide(int b, int c) {
        if (b == 0x80000000 && c == -1) {
            return Integer.MAX_VALUE;
        }

        int negative = 2;
        if (b > 0) {
            negative--;
            b = -b;
        }

        if (c > 0) {
            negative--;
            c = -c;
        }

        int result = core(b, c);
        return negative == 1 ? -result : result;
    }

    private static int core(int b, int c) {
        int result = 0;
        while (b <= c) {
            int q = 1;
            int v = c;
            while (v >= 0xc0000000 && b <= v + v) {
                q += q;
                v += v;
            }
            result += q;
            b -= v;
        }
        return result;
    }

    /**
     * 等价于下面，但是都必须是正数。如果是负数的话需要取绝对值计算
     */
    private static int core2(int b, int c) {
        int result = 0;
        while (b >= c) {
            // 2的零次方
            int q = (int) Math.pow(2, 0);
            int v = c;
            int i = 0;

            // c * 2的n+1次方
            while (b >= c * (int) Math.pow(2, i + 1)) {
                q = (int) Math.pow(2, i + 1);
                v = c * (int) Math.pow(2, i + 1);
                i++;
            }
            result += q;
            b -= v;
        }
        return result;
    }

    private static int core3(int b, int c) {
        int result = 0;
        while (b >= c) {
            // 底数
            int a = 3;
            // 3的零次方
            int q = (int) Math.pow(a, 0);
            int v = c;
            int i = 0;

            // c * a的n+1次方
            while (b >= c * (int) Math.pow(a, i + 1)) {
                q = (int) Math.pow(a, i + 1);
                v = c * (int) Math.pow(a, i + 1);
                i++;
            }
            result += q;
            b -= v;
        }
        return result;
    }

    public static void main(String[] args) {
        int result = divide(15, 2);
        System.out.println(result);
//        int result2 = core2(15, 2);
//        System.out.println(result2);
//        int result3 = core3(35, 6);
//        System.out.println(result3);
    }
}
